/* 
* File:   Joystick.h
* Author: Ben
*
* Created on May 1, 2013, 7:32 PM
*/

#pragma once

#define DIRECTINPUT_VERSION 0x0800

#include <dinput.h>
#include <string>
#include <memory>
#include <vector>

namespace controllers {

	class Joystick {
	public:
		static class Type {
		private:
			DWORD type;
		public:
			Type(DWORD type);
			Type(const Type& orig);

			bool operator==(Type& rhs) const;
			static Type kJoystick;
			static Type kGamepad;
			static Type kKeyboard;
			static Type kUnknown;
		};

		Joystick(const LPDIRECTINPUT8 di, const LPCDIDEVICEINSTANCE dev);
		Joystick(Joystick&& other);
		virtual ~Joystick();

		void create();
		void acquire();
		bool poll();
		const std::wstring& getName() const;
		Type getType() const;
		float getX() const;
		float getY() const;
		bool getTrigger() const;
		bool getRightClick() const;
		bool getScrollUp() const;
		bool getScrollDown() const;

	private:
		static const int kRange = 1000;
		static const BYTE kButtonPressed = 128;

		typedef struct JoystickData { 
			LONG xAxis;
			LONG yAxis;
			BYTE trigger;
			BYTE rightClick;
			BYTE scrollUp;
			BYTE scrollDown;
		private:
			BYTE bPadding[2]; // To make it a DWORD multiple in size
		} JoystickData; 

		explicit Joystick(const Joystick& orig);
		Joystick& operator=(Joystick&& other);

		std::wstring name;
		GUID guid;
		LPDIRECTINPUT8 directInput;
		LPDIRECTINPUTDEVICE8 controller;
		JoystickData data;
		Type type;
		bool acquired;

		static DIOBJECTDATAFORMAT kObjectDataFormat[];
		static const DIDATAFORMAT kDataFormat;
	};
}

